package club.baimahu.pencil.servlet;

import club.baimahu.pencil.servlet.annotation.RequestBody;
import com.alibaba.fastjson.JSONObject;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.List;
import java.util.Map;

/**
 * 将处理器看做执行对象的某个方法
 */
public class SimpleHandler implements Handler{

    private Method method;

    private Object object;

    public SimpleHandler(Method method,Object object){
        this.method = method;
        this.object = object;
    }



    @Override
    public void handle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) {
        //Object[] params = new Object[2];

        Class<?>[] paramClasses = method.getParameterTypes();
        Parameter[] parameters = method.getParameters();

        Object[] params = setParameterValue(httpServletRequest, parameters);


        try {
                Object returnObj = method.invoke(object,params);
                httpServletResponse.write(returnObj);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            } catch (InvocationTargetException e) {
                e.printStackTrace();
        }


    }

    private Object[] setParameterValue(HttpServletRequest httpServletRequest, Parameter[] parameters) {

        Class<?>[] paramClasses = null;
        Object[] params = new Object[parameters.length];
        int i = 0 ;
        for(Parameter parameter : parameters){
            try {
                Class clazz = parameter.getType();
                if(parameter.getAnnotation(RequestBody.class) != null){
                    JSONObject jsonObject = httpServletRequest.getJSON();
                    if(jsonObject != null){
                        Object instance = jsonObject.toJavaObject(clazz);
                        params[i++] = instance;
                        continue;
                    }
                }
                Object o = clazz.newInstance();
                params[i++] = o;
                Field[] fields = clazz.getDeclaredFields();

                Map<String,List<String>> map = httpServletRequest.getParameters();

                for(Field field : fields){
                    for(String key : map.keySet()){
                        if(key.equals(field.getName())){
                            field.setAccessible(true);
                            Class claz = field.getType();
                            String value = map.get(key).get(0);
                            if(claz == Integer.class || claz == int.class){
                                field.setInt(o,Integer.parseInt(value));
                                continue;
                            }
                            if(claz == String.class){
                                field.set(o,value);
                                continue;
                            }
                            if(claz == boolean.class || claz == Boolean.class){
                                field.setBoolean(o,Boolean.parseBoolean(value));
                                continue;
                            }
                            if(claz == float.class || claz == Float.class){
                                field.setBoolean(o,Boolean.parseBoolean(value));
                                continue;
                            }
                            if(claz == Long.class || claz == long.class){
                                field.setBoolean(o,Boolean.parseBoolean(value));
                                continue;
                            }
                            if(claz == Double.class || claz == double.class){
                                field.setBoolean(o,Boolean.parseBoolean(value));
                                continue;
                            }
                            if(claz == Character.class || claz == char.class){
                                field.setBoolean(o,Boolean.parseBoolean(value));
                                continue;
                            }
                            if(claz.isArray()){
                                //只适合String【】
                                field.set(o,map.get(key));
                                continue;
                            }

                        }
                    }
                }

            } catch (InstantiationException e) {
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
        }
        return params;
    }
}
